home *** CD-ROM | disk | FTP | other *** search
- DaoLib 2.0 - A complete solution for real world database development.
-
-
- 1 - Enhancements in this version - Requirements - Getting started
- 2 - Introduction
- 3 - Core components
- 4 - Intermediate abstractions
- 5 - User interface components
- 6 - Tutorial and code samples
- 7 - Deployment
- 8 - Feedback - Support
- 9 - Reference
- 10 - How to purchase
-
-
-
- 1 - Enhancements in this version - Requirements - Getting started
-
- This new version of DaoLib has been rebuilt over the wrapping classes
- for DAO provided by the #import directive of Visual C++ 6.0. This means that
- it makes extensive use of the built-in support for fundamental COM types and
- smart pointers. All this resulted in a more stable and compatible library.
- Unzip the DaoLib file maintaining the directory structure (-d). This
- library requires Visual C++ 6.x installed on the development system. The
- evaluation version is fully functional, with a limit of 10 controls per
- dialog and an annoying reminder.
-
-
-
- 2 - Introduction
-
- The power of the DAO interface for dealing with databases is an
- undeniable fact. It provides a fast and reliable mechanism for data
- management of Access and other ISAM and ODBC databases. Though it was
- engineered targeting scripting languages such as Visual Basic and VBA, it
- provides a dual interface, which allows straightforward C and C++ handling of
- its methods and properties.
-
- The C/C++ developer has several options:
-
- a) Deal with COM interfaces such as DAODatabase, DAORecordset and the
- like using the OS built-in OLE support. This could be tedious and error prone,
- since the developer has to deal with reference counting, object releasing and
- other COM annoying aspects.
-
- b) Go up one level through a C++ proxy. Microsoft provides such a
- proxy-wrapper in its DAO library. This library is rowset-oriented and provides
- a valuable variable binding mechanism, but it is not the best solution for
- handling record-oriented applications.
-
- c) Use some framework which integrates the database specifics with a
- user interface management. MFC-DAO is an example of this approach. The problem
- here is that the integration is best suited for a Doc/View architecture, and
- it adds some complexity when dealing with dialog intensive applications.
-
- DaoLib was built with this three-level separation of concerns. It deals
- with all the COM burden, such as exception handling, reference counting and
- object lifespan. It provides a wrapper level you can access directly, and it
- integrates to MFC with little overhead.
-
-
-
- 3 - Core components
-
- The classes at this level are wrapped around DAO components. In
- addition, you can use helper classes such as _bstr_t, _variant_t and
- Currency, which encapsulate the BSTR, VARIANT and CURRENCY semantics, allowing
- a very robust parameter handling. _com_error manages error handling, converting
- COM error objects into C++ exceptions.
-
- The instantiation of Dao objects was simplified through smart
- constructors, many of which take no arguments or a single string object. The
- enumerator semantics is replaced by a simpler indexing mechanism. The use of
- the 'property' Microsoft extension allows a 'VB-like' syntax in many cases:
- using Variant indexes, you can refer to a specific field as:
- FieldValue[0] or as: FieldValue["CustomerID"]
- In addition, the same property (if marked read/write) can be a left or right
- value.
-
- These are the core components and their mapping to DAO components:
-
- _FieldPtr DAOField
- DaoRecordset DAORecordset
- DatabasePtr DAODatabase
- WorkspacePtr DAOWorkspace
- _DBEnginePtr DAODBEngine
- ParameterPtr DAOParameter
- _QueryDefPtr DAOQueryDef
- _TableDefPtr DAOTableDef
- _IndexPtr DAOIndex
- _UserPtr DAOUser
- _GroupPtr DAOGroup
- _RelationPtr DAORelation
- ConnectionPtr DAOConnection
- PropertyPtr DAOProperty
-
- These are the helper classes and their COM counterparts:
-
- _bstr_t BSTR
- _variant_t VARIANT
- Currency CURRENCY
-
- This has no counterparts:
-
- _com_error Error handling through exception throwing.
-
-
-
- 4 - Intermediate abstractions
-
- In order to connect database objects with user interface elements
- such as controls, windows or dialogs, a couple of intermediate level
- abstract classes must be added to the hierarchy. These are DaoWindow and
- DaoControl. A windowing user interface element must inherit from DaoWindow
- and a control element from DaoControl to have complete control of its
- underlying database objects. They interact tightly with MFC transfer
- mechanisms.
-
-
-
- 5 - User interface components
-
- DaoLib comes with several user interface components, but its open
- architecture allows you to add your own custom components. The basic
- components are:
-
- Windowing components:
-
- DaoDialog
- DaoPropSheet
- DaoPropPage
-
- Control components:
-
- DaoEdit
- DaoCheck
- DaoRadio
- DaoGroup
- DaoCombo
- DaoListCtrl
-
- Complete components:
-
- ListDialog
-
- The windowing components are intended to be used as base classes of
- your dialog objects. You can create regular dialogs or property pages using
- the ClassWizard and then replace the base class in the declaration and add
- the constructor arguments. ClassWizard will still recognize your class and
- it even will use DaoDialog or DaoPropPage when adding base class references.
-
- The control classes can be used directly. Once again, you create
- control objects with ClassWizard and then replace their declaration (you can
- use the 'Replace' command if you have many controls). You can manage some
- attributes of the controls at declaration time, such as enabling or writing
- denial.
-
- DaoLib includes a powerful dialog-based component called ListDialog.
- It manages the display of Recordset objects through a list control, naming
- each header column upon the field's name and formatting the data according
- to each data type. In addition, it provides complete printing support for the
- list control's contents, sorting through column header clicking, keyboard
- support (Insert for adding records, Delete for deleting, Enter for viewing),
- and a mouse driven context menu with those same functions.
-
-
-
- 6 - Tutorial and code samples
-
- The use of the library does not require any special skill. If you use
- Visual C++ and feel comfortable with the ClassWizard, you can produce DaoLib
- code immediately. The steps to follow are:
-
- 1 - You can create a project without database support, or use an
- existing project. Add DaoLib2.lib to the libraries in the project settings
- (Link page). Map the include path accordingly (C/C++ - Preprocessor).
-
-
- 2 - In the declaration of your App class, add the core #include
-
- #include "resource.h" // main symbols
-
- becomes:
-
- #include "resource.h" // main symbols
- #include "bordao.h"
-
-
- 3 - In InitInstance, add the Database initialization:
-
- CMainFrame* pFrame = new CMainFrame;
- m_pMainWnd = pFrame;
-
- becomes:
-
- try {
- OpenDatabase("mydata.mdb"); //full path here, unless same
- //directory as .EXE
- }
- catch(_com_error& e) {
- Show(e);
- return FALSE;
- }
-
- CMainFrame* pFrame = new CMainFrame;
- m_pMainWnd = pFrame;
-
-
- 4 - Create the appropiate dialog resource. Assign each control an ID
- that resembles the name of the field with which it is associated. You can
- optionally add a Modify button (ID = 302). It must be the first in the
- control creation order. You may also add a Enter button (ID = 301). It must
- be non-visible, non-tabstop and marked as default button (unmark the OK
- button).
-
-
- 5 - Open the ClassWizard and create the CDialog as usual. For each
- control, assign a member variable (Category: Control) of the required type.
- If you want to use the macros provided with DaoLib (recommended), give each
- control the exact name of the corresponding field, prefixed with 'm_' (for a
- field named CustomerID it should be m_CustomerID).
-
-
- 6 - Close the ClassWizard and go to the dialog's class declaration
- (*.h file). Replace CDialog with CDaoDialog in the inheritance tag and add
- two parameters to the constructor before the existing one:
-
- class CMyDialog : public CDialog
- {
- // Construction
- public:
- CMyDialog(CWnd* Parent = NULL);
-
- becomes:
-
- class CMyDialog : public CDaoDialog
- {
- // Construction
- public:
- CMyDialog(LPCSTR s = 0, bool a = 0, CWnd* Parent = NULL);
-
-
- 7 - Replace the member control objects with the appropiate ones:
-
- // Dialog Data
- //{{AFX_DATA(CMyDialog)
- enum { IDD = IDD_MYDIALOG };
- CEdit m_CustomerID;
- CButton m_NewCustomer;
-
- becomes:
-
- // Dialog Data
- //{{AFX_DATA(CMyDialog)
- enum { IDD = IDD_MYDIALOG };
- CDaoEdit m_CustomerID;
- CDaoCheck m_NewCustomer;
-
-
- 8 - Go to the implementation file (*.cpp) and add the #includes you
- need before the declaration file #include. In this case:
-
- #include "stdafx.h"
- #include "MyDialog.h"
-
- becomes:
-
- #include "stdafx.h"
- #include "DaoDialog.h"
- #include "DaoEdit.h"
- #include "DaoCheck.h"
- #include "MyDialog.h"
-
-
- 9 - Modify the constructor accordingly.
-
- CMyDialog::CMyDialog(CWnd* pParent /*=NULL*/)
- : CDialog(CMyDialog::IDD, pParent)
- {
-
- becomes:
-
- CMyDialog::CMyDialog(LPCSTR s, bool a, CWnd* pParent /*=NULL*/)
- : CDaoDialog(CMyDialog::IDD, pParent, s, a)
- {
-
-
- 10 - In the body of the constructor, add the initialization macros.
-
- //}}AFX_DATA_INIT
- }
-
- becomes:
-
- //}}AFX_DATA_INIT
- DAOCONTROL(CustomerID);
- DAOCONTROL(NewCustomer);
- }
-
-
- 11 - Replace CDialog in the message map macro with CDaoDialog
-
- BEGIN_MESSAGE_MAP(CMyDialog, CDialog)
- //{{AFX_MSG_MAP(CMyDialog)
-
- becomes:
-
- BEGIN_MESSAGE_MAP(CMyDialog, CDaoDialog)
- //{{AFX_MSG_MAP(CMyDialog)
-
-
- 12 - That's it. Now you can construct an instance of your dialog and
- execute it. This can be done from inside a menu response function:
-
- CString sql = "select * from Customers where CustomerID = 5477";
- try {
- CMyDialog Cust(sql);
- Cust.DoModal();
- }
- catch(_com_error& e) {
- Show(e, *this);
- return;
- }
-
- or, for inserting a record:
-
- CString sql = "select * from Customers";
- try {
- CMyDialog Cust(sql, true);
- Cust.DoModal();
- }
- catch(_com_error& e) {
- Show(e, *this);
- return;
- }
-
- or, if you want to use a ListCtrl:
-
- DaoRecordset rs;
- try {
- rs = "select * from Customers";
- }
- catch(_com_error& e) {
- Show(e, *this);
- return;
- }
- CMyDialog Cust;
- CListDialog Lis(rs, &Cust);
- Lis.SetCaption("Listing of Customers");
- Lis.DoModal();
-
- Don't forget to #include the DaoLib specific headers in this file too,
- before the dialog declaration #include. If you use the ListCtrl component, you
- must add the corresponding resources from DaoLib.rc to your resource file.
-
- #include "DaoDialog.h"
- #include "DaoEdit.h"
- #include "DaoCheck.h"
- #include "MyDialog.h"
- #include "ListDialog.h" //if using ListDialog
-
- If you don't use all the functionality of DaoLib, the linker may issue
- warnings about not referencing some libraries: this is the normal behavior.
- If you compile and link a Debug version, you can get some other warnings about
- conflicting libraries. The non-evaluation version of DaoLib comes with a
- Debug static library and complete source code.
-
-
- 13 - The procedure for a property sheet is very similar. Take a look
- at the accompanying sample code.
-
-
-
- 7 - Deployment
-
- Programs built using DaoLib need no additional dlls. Of course DAO is
- required. A DaoLib license allows unlimited deployment.
-
-
-
- 8 - Feedback - Support
-
- This is not a Beta release: we at ARGSOFT use this library since 1996
- (VC++ 4.2) for our custom products, and it only required some updating from
- time to time. We are aware that other developers may have quite different
- needs, so we will appreciate feedback. Please write to:
-
- feedback@argsoft.com
-
- ARGSOFT provides full support for the registered version. Evaluators
- may ask for support, and in most cases they will get it. Please write to:
-
- support@argsoft.com
-
-
-
- 9 - Reference
-
- In order to avoid repetition, we don't reference methods and
- properties of the core components that are documented in the DAO reference.
- Only those functions with extended functionality are mentioned. You can
- browse header files for more information.
-
- Core components:
-
-
- - DaoRecordset
-
- DaoRecordset();
-
- Default constructor
-
- DaoRecordset(_bstr_t);
-
- Constructs a DaoRecordset object from a SQL string
-
- DaoRecordset(DaoRecordset&);
-
- Copy constructor
-
- DaoRecordset& operator=(_bstr_t);
-
- Assignment operator
-
- - Globals
-
- _variant_t getdate();
-
- Retrieves current date/time
-
- _bstr_t shortdate(_variant_t);
-
- Returns date part
-
-
- Abstract base classes:
-
- - DaoWindow
-
- DaoWindow(LPCSTR s = 0, bool a = false);
-
- Regular constructor. It takes a SQL string and an editing/adding condition.
-
- DaoWindow(DaoRecordset& r, bool a = false);
-
- Constructor for child objects, taking an existing recordset.
-
- bool alta;
-
- Attribute that determines if we are editing or adding a record.
-
- virtual bool Execute() = 0;
-
- Mandatory execution method.
-
- virtual bool Exec(char* sql, bool a = false);
-
- This method launches a dialog object from an external user interface.
-
- virtual bool Baja(char* sql);
-
- Method for managing record deletion
-
- - DaoControl
-
- virtual void Transfer(BOOL bSaveAndValidate) = 0;
-
- This forces derived classes to implement the transfer mechanism.
-
- Variant index;
-
- Attribute for the field class. It can be a field name or a field index.
-
- void DDX_Control(CDataExchange *pDX);
-
- Binding method. It manages collaboration between the GUI and database
- components.
-
- DaoControl& operator=(Variant const &);
-
- Assignment operator. Each derived class must override this.
-
- virtual void Enable(bool e = true) = 0;
-
- User interface enabling/disabling mandatory method.
-
- Windowing user interface:
-
- - CDaoDialog
-
- This class combines a regular CDialog with a DaoWindow interface. It
- trasparently manages several aspects of the user interface, such as
- initialization of control objects, enabling of controls, update or insert of
- data and control navigation.
-
- bool cont;
-
- Attribute for controlling survival of the object after an OnOK event.
- Useful for continued data entry.
-
- bool child;
-
- This condition is true if the object was created with the child
- creation constructor.
-
- CDaoDialog(UINT i, CWnd* p = 0, LPCSTR s = 0, bool a = false);
-
- Normal constructor. It takes the usual CDialog parameters plus a SQL
- string and a insert/update flag.
-
- CDaoDialog(UINT i, DaoRecordset& r, CWnd* p = 0, bool a = false);
-
- Child creation constructor. It references an existing DaoRecordset
- object.
-
- virtual void OnOK();
-
- It manages inserting or updating data.
-
- void SetCaption(LPCTSTR str);
-
- As name suggests.
-
- bool Execute();
-
- Virtual execution member function. Returns true if OK is pressed;
- false otherwise.
-
- void SetModify(int Id, bool mod = true);
-
- Helper function for edit controls.
-
- void SetDlgItemText(int nID, LPCTSTR lpszString);
-
- Override of the CWnd function. It sets the modify flag in edit
- controls.
-
- virtual void OnModificar();
-
- Manages enabling of controls.
-
- virtual void OnEnter();
-
- Moves focus among controls on each return.
-
- - CDaoPropSheet
-
- Objects of this class, unlike CDaoDialog, can be used directly. It
- adapts the functionality of CDaoDialog to property sheets.
-
- CDaoPropSheet(LPCTSTR pszCaption = 0, LPCSTR s = 0, bool a = false,
- CWnd* pParentWnd = NULL);
-
- Constructor. Takes the normal CDaoPropertySheet parameters plus a SQL
- string and an insert/update flag.
-
- bool modif;
-
- Modification flag. It determines enabling of controls.
-
- bool Execute();
-
- Virtual execution method. Returns true if OK is pressed;
- false otherwise.
-
- - CDaoPropPage
-
- This is a base class for property pages linked to CDaoPropSheet
- objects. In addition to the regular CDaoDialog features, it manages wizard
- interfaces for inserting new data.
-
- CDaoPropPage(UINT resId);
-
- Constructor. It takes a resource identification.
-
- bool GetModif() const;
-
- It returns the property sheet modification flag.
-
- void SetModify(int Id,bool mod = true);
-
- Helper function for edit controls.
-
- bool GetAlta() const;
-
- It returns the insert/update flag.
-
- virtual void OnModificar();
-
- Manages enabling of controls.
-
- Control components:
-
- - CDaoCheck
-
- This control binds to a checkbox and a boolean data field.
-
- CDaoCheck& operator=(Variant const & v);
-
- Initialization method. It associates the Field object with an index.
-
- void Enable(bool e = true);
-
- User interface enabling function.
-
- friend void AFXAPI DDX_Control(CDataExchange* pDX, int nIDC, CDaoCheck& rControl);
-
- This global function overrides the regular DDX_Control function for
- this kind of control.
-
- - CDaoCombo
-
- This is a more complicated control: it manages a combo box related to
- a recordset, usually from another table (lookup). It binds to an integer data
- field in the master table.
-
- void Init(_variant_t v, LPCSTR s);
-
- Initialization function. It takes an index for the Field component
- and a SQL string for the DaoRecordset component.
-
- void Enable(bool e = true);
-
- User interface enabling function.
-
- bool Disabled;
-
- Setting this property disables the component.
-
- friend void AFXAPI DDX_Control(CDataExchange* pDX, int nIDC, CDaoCombo& rControl);
-
- This global function overrides the regular DDX_Control function for
- this kind of control.
-
- - CDaoEdit
-
- This control binds to an edit control and a data field of any type.
- Data type conversion is made transparently.
-
- CDaoEdit& operator=(Variant const &);
-
- Initialization method. It associates the Field object with an index.
-
- void Enable(bool e = true);
-
- User interface enabling function.
-
- bool ReadOnly;
-
- Setting this property avoids writing to the component.
-
- friend void AFXAPI DDX_Control(CDataExchange* pDX, int nIDC, CDaoEdit& rControl);
-
- This global function overrides the regular DDX_Control function for
- this kind of control.
-
- - CDaoGroup
-
- This control binds to a group of automatic radio buttons and an integer
- data field.
-
- CDaoGroup& operator=(Variant const & v);
-
- Initialization method. It associates the Field object with an index.
-
- void Enable(bool e = true);
-
- User interface enabling function.
-
- friend void AFXAPI DDX_Control(CDataExchange* pDX, int nIDC, CDaoGroup& rControl);
-
- This global function overrides the regular DDX_Control function for
- this kind of control.
-
- - CDaoRadio
-
- This is a simpler control, managing two auto radio buttons and binding
- to a boolean data field.
-
- CDaoRadio& operator=(Variant const & v);
-
- Initialization method. It associates the Field object with an index.
-
- void Enable(bool e = true);
-
- User interface enabling function.
-
- friend void AFXAPI DDX_Control(CDataExchange* pDX, int nIDC, CDaoRadio& rControl);
-
- This global function overrides the regular DDX_Control function for
- this kind of control.
-
- - CDaoListCtrl
-
- This control binds to a list control and a DaoRecordset. In addition, it
- provides custom test drawing and interfacing to dialogs and property sheets
- for adding and editing data.
-
- CDaoListCtrl(DaoRecordset& r);
-
- Constructor taking a DaoRecordset reference.
-
- int Llenar();
-
- Filling function.
-
- void Linea(int index);
-
- This function takes care of filling each row.
-
- LPCSTR GetIndexText(int index);
-
- This retrieves the text of an item given its index.
-
- int Update(int index);
-
- Updating function.
-
- Complete components:
-
- - CListDialog
-
- This dialog-based class displays the contents of an entire DaoRecordset.
- It formats columns according to the fields of the recordset.
-
- CListDialog(DaoRecordset& r, DaoWindow* d = 0, CWnd* pParent = NULL);
-
- Constructor. It takes a DaoRecordset reference and an optional DaoWindow
- descendant, which it can open for inserting or modifying data.
-
- void SetCaption(LPCSTR str);
-
- As name suggest.
-
- int* lencol;
-
- Optional array of column lengths, for custom formatting.
-
- int indcol;
-
- Optional index for the column used in the WHERE clause of the SQL
- statement.
-
- int* totcol;
-
- Optional array of column indexes. The component computes totals on
- these columns and show them at the bottom of the list, in each corresponding
- column.
-
- CDaoListCtrl m_Lista;
-
- The CDaoListCtrl member.
-
- virtual void OnOK();
-
- If a DaoWindow descendant was specified on construction, the
- component builds a SQL statement for the selected row and executes the dialog
- object.
-
- afx_msg void OnImprimir();
-
- Prints the content of the list control.
-
- Macros:
-
- DAOCONTROL(fieldname)
-
- Initializes the control object. It is included normally in the window
- object's constructor.
-
- DAOCOMBO(fieldname, tablename)
-
- Initializes a DaoCombo object. It takes as arguments the field name
- in the master table and the lookup table name.
-
-
-
- 10 - How to purchase
-
- You can buy the full version of the library online from a secure
- server. Go to http://argsoft.com and follow the 'How to order' link.
-
-
- Buenos Aires, April 1999.
-